#include "malloc.h"
//内存池
#pragma data_alignment=4	
uint8_t MEM1_Base[MEM1_MAX_SIZE];				//内存池


//内存管理表
uint16_t Mem1_Map_Base[MEM1_ALLOC_TABLE];				//内部内存管理表

//内存管理参数
const uint32_t	Mem_Table_Size[SRAM_BANK]={MEM1_ALLOC_TABLE};
const uint32_t Mem_Block_Size[SRAM_BANK]={MEM1_BLOCK_SIZE};
const uint32_t Mem_Max_Size[SRAM_BANK]={MEM1_MAX_SIZE};

//********复制内存
//****des:目的地址
//****src:源地址
//******n:需要复制的内存长度(字节为单位)
void My_Mem_Cpy(void *des,void *src,uint32_t n)
{
		uint8_t *xdes=des;
		uint8_t *xsrc=src;
		while(n--) *xdes++ = *xsrc++;
}
/*********************
**内存管理初始化*******
**所属内存块***********
**********************/
void My_Mem_Set(void *p,uint8_t value,uint32_t count)
{
	uint8_t *xp =p;
		while(count--)
			*xp++=value;
}
//定义内存管理
/*********************
void My_Mem_Init(uint8_t Mem_x)
**内存管理初始化*******
**所属内存块***********
**********************/
void My_Mem_Init(uint8_t Mem_x)
{
		My_Mem_Set(Malloc_Dev.Mem_Map[Mem_x],0,Mem_Table_Size[Mem_x]*2);
		My_Mem_Set(Malloc_Dev.Mem_Base[Mem_x],0,Mem_Max_Size[Mem_x]);
		Malloc_Dev.Mem_Ready[Mem_x]=1;				//初始化完成，就绪
}
/*********************
uint8_t My_Mem_Usagerate(uint8_t Mem_x)
**内存管使用率*******
**所属内存块***********
**********************/
uint8_t My_Mem_Usagerate(uint8_t Mem_x)
{
		uint16_t i,ii;
		for(i=0;i<Mem_Table_Size[Mem_x];i++)
		{
				if(Malloc_Dev.Mem_Map[Mem_x][i])ii++;
		}
	return (ii*100)/Mem_Table_Size[Mem_x];
}
/**/        
struct Mem_Malloc_Dev   Malloc_Dev =
{
	My_Mem_Init,
	My_Mem_Usagerate,
	MEM1_Base,
	Mem1_Map_Base,
	0,
};
//内存分配，内部内存
uint32_t My_Mem_malloc(uint8_t mem_x,uint16_t size)
{
	signed long offset=0;
	uint16_t N_memb;		//需要的内存块数
	uint16_t	C_memb=0;	//连续空内存的块数
	uint16_t i;
	if(!Malloc_Dev.Mem_Ready[mem_x])Malloc_Dev.init(mem_x);
	if(size==0)return 0xFFFFFFFF;
	N_memb=size/Mem_Block_Size[mem_x];	//需要分配内存的块数
	if(size%Mem_Block_Size[mem_x])N_memb++;
	for(offset=Mem_Table_Size[mem_x]-1;offset>=0;offset--)
		{
				if(!Malloc_Dev.Mem_Map[mem_x][offset])C_memb++;//连续空内存的增加
				else C_memb=0;
				if(C_memb==N_memb)
				{
						for(i=0;i<N_memb;i++)
							{
								Malloc_Dev.Mem_Map[mem_x][offset+i]=N_memb;
							}	
						return (offset*Mem_Block_Size[mem_x]);		//返回偏移量
				}
		}
	return 0xFFFFFFFF;
}
//释放内存，本地调用。内部内存
void * My_Mem_Free(uint8_t mem_x,uint16_t offset)
{
	uint32_t i;
	if(!Malloc_Dev.Mem_Ready[mem_x])	
		{Malloc_Dev.init(mem_x);
		return NULL;
		}
	if(offset<Mem_Max_Size[mem_x])		//在内存中的偏移量
		{
                  uint32_t index=offset/Mem_Block_Size[mem_x];	//在内存表的偏移量
                  uint32_t N_memb=Malloc_Dev.Mem_Map[mem_x][index];
                  for(i=0;i<N_memb;i++)
                  {
                    Malloc_Dev.Mem_Map[mem_x][index+i]=0;
                  }
                  return NULL;
		}
	else 
			return NULL;	//超出偏移区
}
//释放内存
void* myfree(uint8_t mem_x,void *ptr)
{
	uint32_t offset;
        void  *p;
		if(ptr==NULL) return NULL;
	offset=(uint32_t)ptr-(uint32_t)Malloc_Dev.Mem_Base[mem_x];
	p=My_Mem_Free(mem_x,offset);
        return p;
}
//分配内存
void *mymalloc(uint8_t mem_x,uint16_t size)
{
	uint32_t offset;
	offset=My_Mem_malloc(mem_x,size);
	if(offset==0xFFFFFFFF)return NULL;
	else return (void *)((uint32_t)Malloc_Dev.Mem_Base[mem_x]+offset);
}
